package com.xyht.sca_s.student_manage_system.modules.teacher.service.impl;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.xyht.sca_s.student_manage_system.common.commonReturn.CommonCodeEnum;
import com.xyht.sca_s.student_manage_system.common.commonReturn.CommonResult;
import com.xyht.sca_s.student_manage_system.common.commonReturn.ResponseResult;
import com.xyht.sca_s.student_manage_system.modules.common.entity.SmsImportTask;
import com.xyht.sca_s.student_manage_system.modules.common.entity.SmsImportTaskDetail;
import com.xyht.sca_s.student_manage_system.modules.common.mapper.SmsImportTaskDetailMapper;
import com.xyht.sca_s.student_manage_system.modules.common.mapper.SmsImportTaskMapper;
import com.xyht.sca_s.student_manage_system.modules.teacher.entity.SmsTeacherAward;
import com.xyht.sca_s.student_manage_system.modules.teacher.entity.SmsTeacherInfo;
import com.xyht.sca_s.student_manage_system.modules.teacher.entity.req.SmsTeacherAwardAddReq;
import com.xyht.sca_s.student_manage_system.modules.teacher.entity.req.SmsTeacherAwardBatchReq;
import com.xyht.sca_s.student_manage_system.modules.teacher.entity.req.SmsTeacherAwardDeletedReq;
import com.xyht.sca_s.student_manage_system.modules.teacher.entity.resp.SmsTeacherAwardResp;
import com.xyht.sca_s.student_manage_system.modules.teacher.mapper.SmsTeacherAwardMapper;
import com.xyht.sca_s.student_manage_system.modules.teacher.mapper.SmsTeacherInfoMapper;
import com.xyht.sca_s.student_manage_system.modules.teacher.service.SmsTeacherAwardService;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.scheduling.annotation.Async;
import org.springframework.scheduling.annotation.AsyncResult;
import org.springframework.stereotype.Service;
import org.springframework.transaction.PlatformTransactionManager;
import org.springframework.transaction.TransactionDefinition;
import org.springframework.transaction.TransactionStatus;
import org.springframework.transaction.support.DefaultTransactionDefinition;

import javax.annotation.Resource;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.Map;
import java.util.concurrent.Future;
import java.util.stream.Collectors;

import static com.xyht.sca_s.student_manage_system.common.util.ParamCheckUtil.isNullOrEmpty;
import static com.xyht.sca_s.student_manage_system.modules.common.constant.TaskDetailReason.REASON_IMPORT_ERR;
import static com.xyht.sca_s.student_manage_system.modules.common.constant.TaskDetailReason.REASON_INVALID_PARAM;
import static com.xyht.sca_s.student_manage_system.modules.common.constant.TaskNameExample.TASK_NAME_TEACHER_AWARD;
import static com.xyht.sca_s.student_manage_system.modules.common.constant.TaskStatus.TASK_STATUS_DONE;
import static com.xyht.sca_s.student_manage_system.modules.common.constant.TaskStatus.TASK_STATUS_ERR;
import static com.xyht.sca_s.student_manage_system.modules.common.constant.TaskTypeConstant.TASK_TYPE_TEACHER_AWARD;

/**
 * <p>
 * 教师获奖信息表 服务实现类
 * </p>
 *
 * @author XYHT
 * @since 2023-09-05
 */
@Service
public class SmsTeacherAwardServiceImpl extends ServiceImpl<SmsTeacherAwardMapper, SmsTeacherAward> implements SmsTeacherAwardService {


    @Autowired
    private SmsTeacherAwardMapper smsTeacherAwardMapper;
    @Autowired
    private SmsTeacherInfoMapper smsTeacherInfoMapper;
    @Autowired
    private SmsImportTaskMapper smsImportTaskMapper;
    @Autowired
    SmsImportTaskDetailMapper smsImportTaskDetailMapper;
    @Resource
    PlatformTransactionManager transactionManager;

    @Override
    @Async
    public Future<ResponseResult> batchAddTeacherAward(Map<String, Object> map, String user_id) {
        JSONObject jsonObject = JSONObject.parseObject(JSON.toJSONString(map));
        List<SmsTeacherAwardBatchReq> teacherAwardList = JSONObject.parseArray(JSON.toJSONString(jsonObject.get("list")), SmsTeacherAwardBatchReq.class);
        if (teacherAwardList == null || teacherAwardList.size() < 1) {
            return new AsyncResult<>(CommonResult.failed(CommonCodeEnum.INVALID_PARAM));
        }

        //创建导入任务
        SmsImportTask smsImportTask = new SmsImportTask();
        smsImportTask.setTaskName(TASK_NAME_TEACHER_AWARD);
        smsImportTask.setUserId(user_id);
        smsImportTask.setTaskType(TASK_TYPE_TEACHER_AWARD);
        smsImportTaskMapper.insert(smsImportTask);
        batchAddTeacherAwardInfo(teacherAwardList, smsImportTask.getId());
        return new AsyncResult<>(CommonResult.success());
    }

    private void batchAddTeacherAwardInfo(List<SmsTeacherAwardBatchReq> teacherAwardList, String id) {

        int OFFSET_ROW = 1;
        int task_status = TASK_STATUS_DONE;
        for (int i = 0; i < teacherAwardList.size(); i++) {
            //开启事务
            DefaultTransactionDefinition dt = new DefaultTransactionDefinition();
            // 嵌套事务 PROPAGATION_REQUIRES_NEW 每次开启一个新的事务
            dt.setPropagationBehavior(TransactionDefinition.PROPAGATION_REQUIRES_NEW);
            // 设置嵌套事务
            TransactionStatus status = transactionManager.getTransaction(dt);
            try {
                SmsTeacherAwardBatchReq storage = teacherAwardList.get(i);
                if (isNullOrEmpty(storage.getTchNo()) || isNullOrEmpty(storage.getAwardName())
                        || isNullOrEmpty(storage.getTchName()) || isNullOrEmpty(storage.getAwardGrade())
                        || isNullOrEmpty(storage.getAwardDescription())) {
                    transactionManager.rollback(status);
                    task_status = TASK_STATUS_ERR;
                    createTeacherImportTaskDetail(id, REASON_INVALID_PARAM, (i + OFFSET_ROW) + "");
                    continue;
                }
                //校验是否是教师
                List<SmsTeacherInfo> smsTeacherInfos = smsTeacherInfoMapper.selectList(new LambdaQueryWrapper<SmsTeacherInfo>()
                        .eq(SmsTeacherInfo::getTchNo, storage.getTchNo()));
                if(smsTeacherInfos == null || smsTeacherInfos.size() < 1){
                        transactionManager.rollback(status);
                        task_status = TASK_STATUS_ERR;
                        createTeacherImportTaskDetail(id, REASON_INVALID_PARAM, (i + OFFSET_ROW) + "");
                        continue;
                }
                SmsTeacherAward addTeacherAward = new SmsTeacherAward();
                BeanUtils.copyProperties(storage, addTeacherAward);
                smsTeacherAwardMapper.insert(addTeacherAward);
                transactionManager.commit(status);
            } catch (Exception e) {
                transactionManager.rollback(status);
                task_status = TASK_STATUS_ERR;
                createTeacherImportTaskDetail(id, REASON_IMPORT_ERR, (i + OFFSET_ROW) + "");
            }finally {
                if (status.isNewTransaction() && !status.isCompleted()) {
                    transactionManager.commit(status);
                }
            }
        }
        SmsImportTask smsImportTask = new SmsImportTask();
        smsImportTask.setId(id);
        smsImportTask.setStatus(task_status);
        smsImportTaskMapper.updateById(smsImportTask);
    }

    private void createTeacherImportTaskDetail(String id, String reason, String row) {
        SmsImportTaskDetail smsImportTaskDetail = new SmsImportTaskDetail();
        smsImportTaskDetail.setTaskId(id);
        smsImportTaskDetail.setFailReason(reason);
        smsImportTaskDetail.setFailRow(row);
        smsImportTaskDetailMapper.insert(smsImportTaskDetail);
    }

    @Override
    public ResponseResult addTeacherAward(SmsTeacherAwardAddReq addReq) {
        if(isNullOrEmpty(addReq.getTchName(),addReq.getTchNo(),addReq.getAwardName(),addReq.getAwardGrade(),addReq.getAwardDescription())){
            return CommonResult.failed(CommonCodeEnum.INVALID_PARAM);
        }
        List<SmsTeacherInfo> smsTeacherInfos = smsTeacherInfoMapper.selectList(new LambdaQueryWrapper<SmsTeacherInfo>()
                .eq(SmsTeacherInfo::getTchNo, addReq.getTchNo()));
        if(smsTeacherInfos == null || smsTeacherInfos.size() < 1){
            return CommonResult.failed(CommonCodeEnum.TEACHER_AWARD_NOT_EXIST);
        }
        SmsTeacherAward addTeacherAward = new SmsTeacherAward();
        BeanUtils.copyProperties(addReq,addTeacherAward);
        smsTeacherAwardMapper.insert(addTeacherAward);
        return CommonResult.success();
    }

    @Override
    public ResponseResult getTeacherAward(String id) {
        if(isNullOrEmpty(id)){
            return CommonResult.failed(CommonCodeEnum.INVALID_PARAM);
        }

        SmsTeacherAward smsTeacherAward = smsTeacherAwardMapper.selectById(id);
        if(smsTeacherAward == null){
            return CommonResult.failed(CommonCodeEnum.TEACHER_AWARD_NOT_EXIST);
        }

        SmsTeacherAwardResp smsTeacherAwardInfoResp = new SmsTeacherAwardResp();
        BeanUtils.copyProperties(smsTeacherAward, smsTeacherAwardInfoResp);
        List<SmsTeacherInfo> smsTeacherInfos = smsTeacherInfoMapper.selectList(new LambdaQueryWrapper<SmsTeacherInfo>()
                .eq(SmsTeacherInfo::getTchNo, smsTeacherAward.getTchNo()));
        if(smsTeacherInfos != null && smsTeacherInfos.size() > 0) {
            SmsTeacherInfo smsTeacherInfo = smsTeacherInfos.get(0);
            String tchTitle = smsTeacherInfo.getTchTitle();
            smsTeacherAwardInfoResp.setTeacherTitle(tchTitle);
            String tchIdCard = smsTeacherInfo.getTchIdCard();
            if(tchIdCard != null) {
                //获取出生年月日
                String birthYear = tchIdCard.substring(6, 10);
                String monthDay = tchIdCard.substring(10, 14);
                //获取当前时间字符串如：2022-1128
                String nowTimeStr = new SimpleDateFormat("yyyy-MMdd").format(new Date());
                String yearNow = nowTimeStr.substring(0, 4);// 当前年份
                String monthDayNow = nowTimeStr.substring(5, 9);// 当前月日
                int age = Integer.parseInt(yearNow) - Integer.parseInt(birthYear);
                //age减一的情况 ：用户月日大于当前月日（开头可以为0的4位数int）
                if (Integer.parseInt(monthDay) > Integer.parseInt(monthDayNow)) {
                    age = age - 1;
                }
                smsTeacherAwardInfoResp.setTchAge(age);
            }
        }
        return CommonResult.success(smsTeacherAwardInfoResp);
    }

    @Override
    public ResponseResult deletedTeacherAward(SmsTeacherAwardDeletedReq deletedReq) {
        if(isNullOrEmpty(deletedReq.getId())){
            return CommonResult.failed(CommonCodeEnum.INVALID_PARAM);
        }
        SmsTeacherAward smsTeacherAward = smsTeacherAwardMapper.selectById(deletedReq.getId());
        if(smsTeacherAward == null){
            return CommonResult.failed(CommonCodeEnum.TEACHER_AWARD_NOT_EXIST);
        }
        smsTeacherAwardMapper.deleteById(deletedReq.getId());
        return CommonResult.success();
    }

    @Override
    public ResponseResult getTeacherAwardList(Integer pageNum, Integer pageSize, String tchName, String awardGrade, String awardName) {
        Page<SmsTeacherAward> page = new Page<>(pageNum,pageSize);
        LambdaQueryWrapper<SmsTeacherAward> queryWrapper = new LambdaQueryWrapper<>();
        if (!isNullOrEmpty(tchName)) {
            queryWrapper.like(SmsTeacherAward::getTchName,tchName);
        }
        if (!isNullOrEmpty(awardGrade)) {
            queryWrapper.like(SmsTeacherAward::getAwardGrade,awardGrade);
        }
        if (!isNullOrEmpty(awardName)) {
            queryWrapper.like(SmsTeacherAward::getAwardName,awardName);
        }
        queryWrapper.orderByAsc(SmsTeacherAward::getCreateTime);
        List<SmsTeacherAwardResp> list = new ArrayList<>();
        smsTeacherAwardMapper.selectPage(page,queryWrapper);
        list = page.getRecords()
                .stream()
                .map(smsTeacherAward -> {
                    SmsTeacherAwardResp smsTeacherAwardResp = new SmsTeacherAwardResp();
                    BeanUtils.copyProperties(smsTeacherAward,smsTeacherAwardResp);
                    List<SmsTeacherInfo> smsTeacherInfos = smsTeacherInfoMapper.selectList(new LambdaQueryWrapper<SmsTeacherInfo>()
                            .eq(SmsTeacherInfo::getTchNo, smsTeacherAward.getTchNo()));
                    if(smsTeacherInfos != null && smsTeacherInfos.size() > 0) {
                        SmsTeacherInfo smsTeacherInfo = smsTeacherInfos.get(0);
                        String tchTitle = smsTeacherInfo.getTchTitle();
                        smsTeacherAwardResp.setTeacherTitle(tchTitle);
                        String tchIdCard = smsTeacherInfo.getTchIdCard();
                        if (tchIdCard != null) {
                            //获取出生年月日
                            String birthYear = tchIdCard.substring(6, 10);
                            String monthDay = tchIdCard.substring(10, 14);
                            //获取当前时间字符串如：2022-1128
                            String nowTimeStr = new SimpleDateFormat("yyyy-MMdd").format(new Date());
                            String yearNow = nowTimeStr.substring(0, 4);// 当前年份
                            String monthDayNow = nowTimeStr.substring(5, 9);// 当前月日
                            int age = Integer.parseInt(yearNow) - Integer.parseInt(birthYear);
                            //age减一的情况 ：用户月日大于当前月日（开头可以为0的4位数int）
                            if (Integer.parseInt(monthDay) > Integer.parseInt(monthDayNow)) {
                                age = age - 1;
                            }
                            smsTeacherAwardResp.setTchAge(age);
                        }
                    }
                    return smsTeacherAwardResp;
                })
                .collect(Collectors.toList());
        int total = (int) page.getTotal();
        return CommonResult.success(list,total);
    }
}
